import UIKit


class Single {
    private static let lock = DispatchSemaphore.init(value: 1)
    
    public static func shared() -> Single{
        if let shared = _shared {
            return shared
        }
        lock.wait()
        print(" shared start \(Thread.current)")
        defer{
            print(" shared end \(Thread.current)")
            lock.signal()
        }
        if let shared = _shared {
            return shared
        }
        let dbModel = Single()
        _shared = dbModel ;
        return dbModel
    }
    
    public static func release(){
        lock.wait()
        defer{
            lock.signal()
        }
        _shared = nil
    }
    
    private static var _shared : Single? = Single()
}

var index : Int = 100
repeat {
    if((index % 5) == 0){
        DispatchQueue.global().async {
            Single.release()
        }
    }else {
        DispatchQueue.global().async {
            print(" idx = \(index)  \(Single.shared())")
        }
    }
    index -= 1
} while index > 0
